import Utils (readInt, tok, at)
import Data.List (sort)

type Rule =  (Int, Int, Int)
type Table = [Rule]

-- 52 50 48
parseRule :: String -> Rule
parseRule str 
    (src, dst, len)
    where
        (src, dst, len) = (numbers !! 1, numbers !! 0, numbers !! 2)
        numbers = map readInt . tok " " $ str

lookup' :: Table -> Int -> Int
lookup' [] x = x
lookup' ((src, dst, len):ms) x
    | (x >= src) && (x < src + len) = dst + x - src
    | otherwise                     = lookup' ms x

-- seeds: 79 14 55 13
getSeeds :: [String] -> [Int]
getSeeds input = map readInt . tok " " . at 1 . tok ":" . at 0 & input

main = do
    contents <- readFile "input.txt"
    
    let seeds = getSeeds . lines $ contents

    let tables = map (map parseRule)
               . map tail
               . tok [""]
               . drop 2
               . lines $ contents

    let locations = map (lookup' (tables !! 6))
                  . map (lookup' (tables !! 5))
                  . map (lookup' (tables !! 4))
                  . map (lookup' (tables !! 3))
                  . map (lookup' (tables !! 2))
                  . map (lookup' (tables !! 1))
                  . map (lookup' (tables !! 0))
                  $ seeds

    print $ minimum locations

    